package com.example.myapplication;

import android.content.Context;
import android.content.Intent;
import android.content.res.Configuration;
import android.os.Bundle;
import android.widget.FrameLayout;
import android.widget.Toast;

import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;

import org.json.JSONObject;

import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Map;

import io.flutter.app.FlutterActivityDelegate;
import io.flutter.app.FlutterActivityEvents;
import io.flutter.facade.Flutter;
import io.flutter.plugin.common.MethodCall;
import io.flutter.plugin.common.MethodChannel;
import io.flutter.plugin.common.PluginRegistry;
import io.flutter.view.FlutterNativeView;
import io.flutter.view.FlutterView;

/** 显示flutter view的根activity */
public class FlutterActivity extends AppCompatActivity implements FlutterView.Provider, PluginRegistry, FlutterActivityDelegate.ViewFactory {

    private FlutterView flutterView;

    private static final String CHANNEL_NATIVE = "com.example.flutter/native";
    private static final String CHANNEL_FLUTTER = "com.example.flutter/flutter";

    protected  void initFlutterView(String initalRoute) {
        initFlutterView(initalRoute, "");
    }

    protected  void initFlutterView(String initalRoute, JSONObject data) {
        initFlutterView(initalRoute, data == null ? "" : data.toString());
    }

    /**
     * 初始化 Flutter View
     * @param initalRoute  要转到的页面
     * @param data  传入的参数
     */
    protected void initFlutterView(String initalRoute, String data) {
        // 根据不同的route创建不同的组件
        String route = initalRoute == null ? "/" : initalRoute;
        if (data != null && !data.isEmpty()) {
            route = route + "?" + data;
        }
        flutterView = Flutter.createView(this, this.getLifecycle(), route);
        FrameLayout.LayoutParams layout = new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, FrameLayout.LayoutParams.MATCH_PARENT);
        addContentView(flutterView, layout);
    }

    private static final String TAG = "FlutterActivity";
    private final FlutterActivityDelegate delegate = new FlutterActivityDelegate(this, this);
    private FlutterActivityEvents eventDelegate;
    private FlutterView.Provider viewProvider;
    private PluginRegistry pluginRegistry;

    public FlutterView getFlutterView() {
        return this.viewProvider.getFlutterView();
    }

    public final boolean hasPlugin(String key) {
        return this.pluginRegistry.hasPlugin(key);
    }

    public final <T> T valuePublishedByPlugin(String pluginKey) {
        return this.pluginRegistry.valuePublishedByPlugin(pluginKey);
    }

    public final Registrar registrarFor(String pluginKey) {
        return this.pluginRegistry.registrarFor(pluginKey);
    }

    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        this.eventDelegate = this.delegate;
        this.viewProvider = this.delegate;
        this.pluginRegistry = this.delegate;

        //this.eventDelegate.onCreate(savedInstanceState);
        initFlutterView(this.getIntent().getStringExtra("route"), this.getIntent().getStringExtra("data"));

        MethodChannel nativeChannel = new MethodChannel(flutterView, CHANNEL_NATIVE);
        nativeChannel.setMethodCallHandler(new MethodChannel.MethodCallHandler() {
            @Override
            public void onMethodCall(MethodCall methodCall, MethodChannel.Result result) {
                switch (methodCall.method) {
                    case "goBack":
                        // 返回上一页
                        finish();
                        break;
                    case "goBackWithResult":
                        // 返回上一页，携带数据
                        Intent backIntent = new Intent();
                        backIntent.putExtra("message", (String) methodCall.argument("message"));
                        setResult(RESULT_OK, backIntent);
                        finish();
                        break;
                    case "jumpToNative":
                        // 跳转原生页面
                        // 这里可以根据name来判断应该转向那个原生页
                        Toast.makeText(getBaseContext(), methodCall.arguments.toString(), Toast.LENGTH_LONG).show();
                        Intent jumpToNativeIntent = new Intent(FlutterActivity.this, NativePageActivity.class);
                        jumpToNativeIntent.putExtra("name", (String) methodCall.argument("name"));
                        startActivityForResult(jumpToNativeIntent, 0);
                        break;
                    default:
                        result.notImplemented();
                        break;
                }
            }
        });

        // 反射设置eventDelegate
        Field declaredField = null;
        try {
            declaredField = this.eventDelegate.getClass().getDeclaredField("flutterView");
            declaredField.setAccessible(true);
            declaredField.set(this.eventDelegate, flutterView);
        } catch (NoSuchFieldException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }
    }

    protected void onStart() {
        super.onStart();
        this.eventDelegate.onStart();
    }

    protected void onResume() {
        super.onResume();
        this.eventDelegate.onResume();
    }

    protected void onDestroy() {
        //this.eventDelegate.onDestroy();
        super.onDestroy();
    }

    public void onBackPressed() {
        if (!this.eventDelegate.onBackPressed()) {
            // super.onBackPressed();
            MethodChannel flutterChannel = new MethodChannel(flutterView, CHANNEL_FLUTTER);
            flutterChannel.invokeMethod("goBack", null);
        }

    }

    protected void onStop() {
        this.eventDelegate.onStop();
        super.onStop();
    }

    protected void onPause() {
        super.onPause();
        this.eventDelegate.onPause();
    }

    protected void onPostResume() {
        super.onPostResume();
        this.eventDelegate.onPostResume();
    }

    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
        this.eventDelegate.onRequestPermissionsResult(requestCode, permissions, grantResults);
    }

    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        if (!this.eventDelegate.onActivityResult(requestCode, resultCode, data)) {
            super.onActivityResult(requestCode, resultCode, data);
            switch (requestCode) {
                case 0:
                    if (data != null) {
                        String message = data.getStringExtra("message");
                        Map<String, Object> result = new HashMap<>();
                        result.put("message", message);
                        // 创建MethodChannel，这里的flutterView即Flutter.createView所返回的View
                        MethodChannel flutterChannel = new MethodChannel(flutterView, CHANNEL_FLUTTER);
                        flutterChannel.invokeMethod("onActivityResult", result);
                    }
                    break;
                default:
                    break;
            }
        }

    }

    protected void onNewIntent(Intent intent) {
        this.eventDelegate.onNewIntent(intent);
    }

    public void onUserLeaveHint() {
        this.eventDelegate.onUserLeaveHint();
    }

    public void onTrimMemory(int level) {
        this.eventDelegate.onTrimMemory(level);
    }

    public void onLowMemory() {
        this.eventDelegate.onLowMemory();
    }

    public void onConfigurationChanged(Configuration newConfig) {
        super.onConfigurationChanged(newConfig);
        this.eventDelegate.onConfigurationChanged(newConfig);
    }

    @Override
    public FlutterView createFlutterView(Context context) {
        return flutterView;
    }

    @Override
    public FlutterNativeView createFlutterNativeView() {
        return null;
    }

    @Override
    public boolean retainFlutterNativeView() {
        return false;
    }
}
